use anyhow::{ ensure, Result };
use fudata::model::kline::Klt;
use fudata::model::security;

use crate::stock::stock_kline_craw;

///
///
/// code: e.g. "000001", "300529", "600519", "688063", "837046"
///
/// end : str, 结束日期， '20500101' ，表示 2050年1月1日
///
/// klt : u32,
///    行情之间的时间间隔，可选示例如下
///    - ``5``      : 5 分钟
///    - ``15``     : 15分钟
///    - ``30``     : 30分钟
///    - ``60``     : 60分钟
///    - ``101``    : 日
///    - ``102``    : 周
///    - ``103``    : 月
///
/// fqt : u16,
///    复权方式，可选示例如下
///    - ``0`` : 不复权
///    - ``1`` : 前复权
///    - ``2`` : 后复权
///
/// lmt : u16,
///    一次性获取记录个数,从 end 结束日期倒数
///
/// 如果更关注价格的实时变动和交易机会，可以选择前复权；如果需要进行历史数据回测和计算收益率，那么后复权可能更为合适。
///
pub async fn update_etf_kline_from_eastmoney(
    security: &security::Security,
    end: &str,
    klt: &Klt,
    fqt: u16,
    lmt: u32
) -> Result<u32> {
    ensure!(
        &security.type_ == &security::SecurityType::ETF,
        format!(
            "(update_etf_kline_from_eastmoney) invalid type_, only ETF security: {:?}",
            security
        )
    );
    stock_kline_craw::get_and_update_stock_kline_from_eastmoney(security, end, klt, fqt, lmt).await
}

#[cfg(test)]
mod test {
    use fudata::db;
    use fudata::model::kline::Klt;
    use fudata::model::security;

    use crate::fund::etf_kline_craw;

    #[tokio::test]
    async fn test_update_etf_kline_from_eastmoney() {
        let _ = db::init().await.unwrap();

        let securities = db::security
            ::select(&None, Some(security::SecurityType::ETF), None, None, 0, 1).await
            .unwrap();

        let klts = [Klt::M005, Klt::M015, Klt::M030, Klt::M060, Klt::DAY, Klt::WEEK, Klt::MONTH];

        for security in securities.iter() {
            for klt in &klts {
                let rs = etf_kline_craw::update_etf_kline_from_eastmoney(
                    &security,
                    "20500101",
                    klt,
                    1,
                    3
                ).await;
                println!("rs={:?} security.id={:?}", rs, security.id);
                assert_eq!(rs.is_ok(), true);
                // assert_eq!(rs.ok().unwrap().len(), 10)
            }
        }
    }
}
